import cn from 'classnames';
import PropTypes from 'prop-types';
import React from 'react';
import { Redirect } from 'react-router-dom';
import Select from '@kuiper-components/select';
import Tabs, { TabPane } from '@kuiper-components/tabs';
import fetch from 'API/fetch';
import Confirm from '@knownsec/react-component/dist/Confirm';
import Loading from '@knownsec/react-component/dist/Loading';
import Download from './DownFiles/Download';
import Weakness from './Weakness';
import Aviliable from './Aviliable';
import SecurityEvent from './SecurityEvent';
import Asset from './Asset';
import s from './style.module.css';
import Overview from './Overview';
import Nonsupport from '../../components/Nonsupport';
import Content from './Content';
import ChangeCheck from './ChangeCheck';
const { Option } = Select;
class Dashboard extends React.PureComponent {
	static propTypes = {
		className: PropTypes.string,
		preview: PropTypes.bool,
		match: PropTypes.shape({
			path: PropTypes.string.isRequired,
			params: PropTypes.shape({
				jobId: PropTypes.string,
				taskCategory: PropTypes.string,
			}),
		}).isRequired,
		history: PropTypes.shape({
			replace: PropTypes.func.isRequired,
		}).isRequired,
		jobList: PropTypes.shape({
			JobMany: PropTypes.arrayOf(
				PropTypes.shape({
					_id: PropTypes.string,
					target: PropTypes.shape({
						host: PropTypes.string.isRequired,
					}),
				})
			),
		}).isRequired,
		data: PropTypes.shape({
			JobOne: PropTypes.shape({
				_id: PropTypes.string,
				assetId: PropTypes.string,
				note: PropTypes.string,
				target: PropTypes.shape({
					host: PropTypes.string.isRequired,
					protocol: PropTypes.string.isRequired,
				}),
				httpResult: PropTypes.array,
				pingResult: PropTypes.array,
				vulResult: PropTypes.object,
				ignoredWarnIdMap: PropTypes.object,
				httpPrevResult: PropTypes.array,
				pingPrevResult: PropTypes.array,
				vulPrevResult: PropTypes.array,
				pingSettings: PropTypes.array,
				httpSettings: PropTypes.array,
				asset: PropTypes.shape({
					_id: PropTypes.string,
					result: PropTypes.object,
					prevResult: PropTypes.object,
				}),
			}),
		}),
	};

	static defaultProps = {
		className: '',
		preview: false,
	};

	state = {
		loading: true,
		tabActiveKey: 'weakness',
		nameList: {},
		name: '',
		JobMany: [],
		job: {},
		jobId: this?.props?.match?.params?.jobId
			? this?.props?.match?.params?.jobId === ':jobId'
				? ''
				: this?.props?.match?.params?.jobId
			: '',
		category: this?.props?.match?.params?.taskCategory,
	};

	selectJob = jobId => {
		const {
			match,
			history: { replace },
		} = this.props;
		if (match.path !== '/dashboard/center/' && jobId) {
			replace(
				match.path
					.replace(':taskCategory?', match?.params?.taskCategory || 'weakness')
					.replace(':jobId', jobId)
			);
		}
		this.getData(jobId, false);
	};

	getAssetList = () => {
		this.setState({
			loading: true,
		});
		fetch(`/api/v2/asset/verified-asset`, {
			method: 'GET',
		})
			.then(resj => {
				const j = resj?.data?.JobMany || [];
				const jobObj = j?.reduce((res, job) => {
					if (res[job.note]) {
						res[job.note].push(job);
					} else {
						res[job.note] = [].concat(job);
					}
					return res;
				}, {});
				if (Object.values(jobObj).length > 0) {
					const o = Object.values(jobObj)[0][0] || {};
					const { jobId } = this?.props?.match?.params;
					const jobId_ = jobId === ':jobId' ? '' : jobId;
					const getId = jobId_ || o.id || '';
					if (getId) {
						this.getData(getId, true);
					}
				}
				this.setState({
					nameList: jobObj,
					JobMany: j,
				});
			})
			.finally(() => {
				this.setState({
					loading: false,
				});
			});
	};

	getData = (item, flag) => {
		if (item) {
			this.setState({
				loading: true,
			});
			fetch(`/api/v2/repodatas/jobone?jobId=${item}`, {
				method: 'GET',
			}).then(res => {
				this.setState({
					loading: false,
					job: res?.data?.jobOne || {},
					jobId: item,
					name: res?.data?.jobOne?.note,
				});
			});
			if (flag) {
				this.selectJob(item);
			}
		}
	};

	componentDidMount() {
		this.getAssetList();
	}

	handleTabChange = category => {
		const { history, match } = this.props;
		this.setState({ category: category });
		history.replace(
			match.path
				.replace(':taskCategory?', category)
				.replace(':jobId', match?.params?.jobId)
		);
	};

	downBack = () => {
		const { history } = this.props;
		Confirm({
			title: '提示',
			className: s.w472,
			message: (
				<div className={s.p20_40}>正在导出报告，您可前往报告任务列表获取。</div>
			),
			cancelText: '',
			confirmText: '报告列表',
			onconfirm: async () => {
				history.push(`/dashboard/downList`);
			},
		});
	};

	selectName = name => {
		const jobList = this.state.nameList[name];
		let id = '';
		if (jobList && jobList.length > 0) {
			id = this.state.nameList[name][0].id;
			this.selectJob(id);
		}
		this.setState({ name, jobId: id });
	};

	contentRef = React.createRef();

	getDropdownRef = () => {
		return this.contentRef.current;
	};

	render() {
		const { nameList, name, job, jobId, category, loading } = this.state;
		const {
			className,
			preview,
			match: { path, params },
		} = this.props;
		const category_ = category === ':taskCategory' ? 'weakness' : category;
		const taskCategory_ =
			params?.taskCategory === ':taskCategory'
				? 'weakness'
				: params?.taskCategory;
		const matchPath =
			path === '/dashboard/center/'
				? '/dashboard/center/:jobId/:taskCategory?'
				: path;
		const firstJobId = this.state.JobMany[0]?.id;
		if (!jobId && firstJobId) {
			return (
				<Redirect
					to={matchPath
						.replace(':taskCategory', taskCategory_)
						.replace(':jobId', firstJobId)}
				/>
			);
		}
		if (!this.state.category) {
			return (
				<Redirect
					to={matchPath
						.replace(':taskCategory', taskCategory_)
						.replace(':jobId', this.state.jobId || firstJobId || ' ')}
				/>
			);
		}
		const resD = JSON.parse(sessionStorage.resD).feature;

		const RtWeakness = type => {
			if (
				resD.sslManualTask ||
				resD.sslTask ||
				resD.vulManualTask ||
				resD.vulTask
			) {
				return (
					<Weakness
						key={job._id}
						result={job.vulResult}
						prevResult={job.vulPrevResult}
						sslResult={job?.sslResult || {}}
						sslPrevResult={job?.sslPrevResult || {}}
						jobId={job._id}
						type={type}
						protocol={job?.target?.protocol}
						ignoredWarnIdMap={job.ignoredWarnIdMap}
						getDropdownRef={this.getDropdownRef}
					/>
				);
			} else {
				return (
					<div className={s.noBox}>
						<Nonsupport className={s.fff}></Nonsupport>
					</div>
				);
			}
		};
		const RtSecurityEvent = () => {
			if (resD.securityEventManualTask || resD.securityEventTask) {
				return (
					<SecurityEvent
						getDropdownRef={this.getDropdownRef}
						key={job._id}
						jobId={job._id}
						result={job.securityEventResult}
						prevResult={job.securityEventPrevResult}
					/>
				);
			} else {
				return (
					<div className={s.noBox}>
						<Nonsupport className={s.fff}></Nonsupport>
					</div>
				);
			}
		};
		const RtContent = () => {
			if (resD.contentManualTask || resD.contentTask) {
				return (
					<Content
						key={job._id}
						jobId={job?._id}
						lastId={job?.contentResultId}
						prevId={job?.contentPrevResultId}
					/>
				);
			} else {
				return (
					<div className={s.noBox}>
						<Nonsupport className={s.fff}></Nonsupport>
					</div>
				);
			}
		};
		const RtChangeCheck = () => {
			if (resD.changeCheckTask) {
				return <ChangeCheck key={job._id} jobId={job?._id} />;
			} else {
				return (
					<div className={s.noBox}>
						<Nonsupport className={s.fff}></Nonsupport>
					</div>
				);
			}
		};

		const RtAviliable = () => {
			if (resD.httpTask || resD.pingTask) {
				return (
					<Aviliable
						key={job._id}
						jobId={job._id}
						httpResult={job.httpResult}
						pingResult={job.pingResult}
						httpPrevResult={job.httpPrevResult}
						pingPrevResult={job.pingPrevResult}
						httpSettings={job.httpSettings}
						pingSettings={job.pingSettings}
						getDropdownRef={this.getDropdownRef}
					/>
				);
			} else {
				return (
					<div className={s.noBox}>
						<Nonsupport className={s.fff}></Nonsupport>
					</div>
				);
			}
		};
		const RtAsset = () => {
			if (resD.assetManualTask || resD.assetTask) {
				return (
					<Asset
						key={job._id}
						assetId={job.assetId}
						result={job?.asset?.result}
						prevResult={job?.asset?.prevResult}
						getDropdownRef={this.getDropdownRef}
					/>
				);
			} else {
				return (
					<div className={s.noBox}>
						<Nonsupport className={s.fff}></Nonsupport>
					</div>
				);
			}
		};
		return (
			<div className={cn(className, s.dataReport)} ref={this.contentRef}>
				<div className={s.header}>
					<div className={s.title}>ScanV监测报表</div>
					<div className={s.selectContainer}>
						<div className={s.left} />
						<span className={cn(s.center, s.mr)}>
							<div className={s.label}>资产名称</div>
							<Select
								size="large"
								value={name}
								className={s.select}
								onChange={this.selectName}
								placeholder="请选择资产名称"
								disabled={preview}
								getPopupContainer={this.getDropdownRef}
							>
								{(Object.keys(nameList) || []).map(n => (
									<Option key={n} value={n}>
										{n}
									</Option>
								))}
							</Select>
						</span>
						<span className={cn(s.center, s.w25rem)}>
							<div className={s.label}>资产地址</div>
							<Select
								key={name}
								size="large"
								value={jobId}
								className={s.select}
								onChange={this.selectJob}
								placeholder="请选择资产"
								disabled={preview}
								getPopupContainer={this.getDropdownRef}
							>
								{(nameList[name] || []).map(item => {
									return (
										<Option key={item.id} value={item.id}>
											{item.targetUrl +
												(item.sourceIp ? `(${item.sourceIp})` : '')}
										</Option>
									);
								})}
							</Select>
						</span>

						<div className={s.right}>
							{!preview && (
								<Download
									note={job?.note || ''}
									target={job?.targetUrl || {}}
									jobId={job?._id}
									className={s.btn}
									nameList={nameList}
									downBack={this.downBack}
								/>
							)}
						</div>
					</div>
				</div>
				<div className={s.content}>
					<Loading label="" show={loading} />
					<Overview
						className={s.overview}
						jobId={job._id}
						assetId={job?.assetId}
					/>
					<Tabs
						className={s.tabs}
						activeKey={category_}
						onChange={this.handleTabChange}
					>
						<TabPane key="weakness" tab="Web漏洞">
							{RtWeakness('weakness')}
						</TabPane>
						<TabPane key="ssl" tab="SSL安全">
							{RtWeakness('ssl')}
						</TabPane>
						<TabPane key="securityEvent" tab="安全事件">
							{RtSecurityEvent()}
						</TabPane>
						<TabPane key="content" tab="内容违规">
							{RtContent()}
						</TabPane>
						<TabPane key="changeCheck" tab="篡改">
							{RtChangeCheck()}
						</TabPane>
						<TabPane key="aviliable" tab="可用性">
							{RtAviliable()}
						</TabPane>
						<TabPane key="asset" tab="Web资产变动">
							{RtAsset()}
						</TabPane>
						<TabPane key="host" tab="主机漏洞">
							{RtWeakness('host')}
						</TabPane>
					</Tabs>
				</div>
			</div>
		);
	}
}

export default Dashboard;
